const { execSync } = require("child_process");
const fs = require("fs");
const path = require("path");
const { FFMPEG_PATH } = require("./ffmpeg");
const { loadConfig } = require("./config");

const config = loadConfig();
const waveformConfig = config.waveform || {
  enabled: false,
  height: 100,
  color: "00ff00",
  position: "bottom",
};

/**
 * Generate waveform video from audio track with transparent background
 * @param {string} inputVideoPath - Path to the input video file
 * @param {string} outputWaveformPath - Path to save the waveform video
 * @returns {boolean} Success status
 */
function generateWaveformVideo(inputVideoPath, outputWaveformPath) {
  try {
    const { videoWidth } = config.projectSettings;
    const waveformHeight = waveformConfig.height || 100;
    const waveformColor = waveformConfig.color || "00ff00";

    // Ensure the output directory exists
    const outputDir = path.dirname(outputWaveformPath);
    if (!fs.existsSync(outputDir)) {
      fs.mkdirSync(outputDir, { recursive: true });
    }

    // Generate waveform video command (fastest approach)
    // Just generate the waveform without any alpha channel processing
    const command = `"${FFMPEG_PATH}" -loglevel error -i "${inputVideoPath}" -filter_complex "[0:a]showwaves=s=${videoWidth}x${waveformHeight}:mode=cline:scale=cbrt:colors=${waveformColor}" -c:v libx264 -preset ultrafast -y "${outputWaveformPath}"`;

    console.log("  Generating waveform video with transparent background...");
    // Execute command and only show stderr (error output)
    execSync(command, { stdio: ["ignore", "ignore", "inherit"] });

    return fs.existsSync(outputWaveformPath);
  } catch (error) {
    console.error("  Error generating waveform video:", error.message);
    return false;
  }
}

/**
 * Overlay waveform video onto the main video
 * @param {string} inputVideoPath - Path to the input video file
 * @param {string} waveformVideoPath - Path to the waveform video file
 * @param {string} outputVideoPath - Path to save the final video with waveform
 * @returns {boolean} Success status
 */
function overlayWaveformVideo(inputVideoPath, waveformVideoPath, outputVideoPath) {
  try {
    // Ensure the output directory exists
    const outputDir = path.dirname(outputVideoPath);
    if (!fs.existsSync(outputDir)) {
      fs.mkdirSync(outputDir, { recursive: true });
    }

    // Overlay command with color keying to make black background transparent
    // Using colorkey filter to make black (0x000000) transparent when overlaying
    const command = `"${FFMPEG_PATH}" -loglevel error -i "${inputVideoPath}" -i "${waveformVideoPath}" -filter_complex "[1:v]colorkey=0x000000:0.3:0.1[ckout];[0:v][ckout]overlay=0:main_h-overlay_h" -c:a copy -y "${outputVideoPath}"`;

    console.log("  Overlaying waveform video onto main video...");
    // Execute command and only show stderr (error output)
    execSync(command, { stdio: ["ignore", "ignore", "inherit"] });

    return fs.existsSync(outputVideoPath);
  } catch (error) {
    console.error("  Error overlaying waveform video:", error.message);
    return false;
  }
}

/**
 * Add waveform to existing video
 * @param {string} inputVideoPath - Path to the input video file
 * @param {string} outputVideoPath - Path to save the final video with waveform
 * @param {number} duration - Duration of the video in seconds
 * @returns {boolean} Success status
 */
function addWaveformToVideo(inputVideoPath, outputVideoPath) {
  if (!waveformConfig.enabled) {
    console.log("  Waveform feature is disabled in config");
    return false;
  }

  try {
    const tempDir = path.join(__dirname, "../../temp");
    if (!fs.existsSync(tempDir)) {
      fs.mkdirSync(tempDir, { recursive: true });
    }

    const waveformVideoPath = path.join(tempDir, "waveform.mp4");

    // Step 1: Generate waveform video
    console.log("  Step 1: Generating waveform video...");
    if (!generateWaveformVideo(inputVideoPath, waveformVideoPath)) {
      console.error("  Failed to generate waveform video");
      return false;
    }

    // Step 2: Overlay waveform onto main video
    console.log("  Step 2: Overlaying waveform onto main video...");
    if (!overlayWaveformVideo(inputVideoPath, waveformVideoPath, outputVideoPath)) {
      console.error("  Failed to overlay waveform video");
      return false;
    }

    // Clean up temporary waveform file
    if (fs.existsSync(waveformVideoPath)) {
      fs.unlinkSync(waveformVideoPath);
    }

    console.log("Successfully added waveform to video");
    return true;
  } catch (error) {
    console.error("Error adding waveform to video:", error.message);
    return false;
  }
}

module.exports = {
  addWaveformToVideo,
};
